use wasm_bindgen::JsValue;
use web_sys::CanvasRenderingContext2d;

/*
    4分音符为1拍，8分音符为半拍，16分音符为四分之一拍

    电子版拇指琴谱，根据拇指琴普手工编写，格式为：

    音符,音符..;时值|音符,音符..;时值|...

    音符解析流程：
    1、根据BPM，计算每组音符应该弹奏的时间点
        1分音符为四拍
        2分音符为两拍
        4分音符为一拍
        8分音符为半拍
        16分音符发为四分之一拍
        每分钟85拍，那么一个8分音符的时长为 (1000*60)/bpm*(4/8)
    2、开始播放，释放第1组音符，记录开始时间
    3、每个音符按一定帧率往下移动
    4、重复释放音符，直到全部音符都播完。

    */

/// P 是休止符
pub const KEYS:&[&str] = &["D6", "B5", "G5", "E5", "C5", "A4", "F4", "D4", "C4", "E4", "G4", "B4", "D5", "F5", "A5", "C6", "E6", "P"];

/// 《蝶恋》 部分
pub const DIELIAN:&str = r#"
E5,E4;8|E5;8|E5;8|D5;8|E5;8|E4;8|A4;8|E5;8|
D4,D5;8|E5;8|D5;8|D5;8|A4,F4;4|A4;8|B4;8|
C5,A4;4|D5;8|C5;8|D4,B4;4|A4;8|G4;8|
A4;8|E4;8|A4;8|B4;8|C5;8|B4;8|C5;8|D5;8|
E5,E4;8|E5;8|E5;8|D5;8|E5;8|E4;8|A4;8|A5;8|
G5,G4;8|A5;8|G5;8|G5;8|D5;4|D5;8|E5;8|
F4,F5;8|A4;8|G5;8|F5;8|E5;8|E4;8|D5;8|C5;8|
E5;8|E4;8|A4;8|B4;8|C5;8|B4;8|C5;8|E5;8|
A5;8|A4;8|B5;8|A5;8|G5;8|E4;8|G4;8|E5;8|
G5;8|E4;8|G4;8|A4;8|B4;8|C5;8|E5;8|G5;8
            "#;

//"D6", "B5", "G5", "E5", "C5", "A4", "F4", "D4", "C4", "E4", "G4", "B4", "D5", "F5", "A5", "C6", "E6", "P"
//"2..","7.", "5.", "3.", "1.", "6",  "4",  "2",  "1",  "3",  "5",  "7",  "2.", "4.", "6.", "1..","3..", "P"

// 简谱中, 8分音符1个下划线, 16分音符2个下划线，4分音符无下划线(1拍)，2分音符右边1横,

/// 《逍遥叹》部分
pub const XIAOYAOTAN:&str = r#"
G4;8;岁|E5;8;月|
D5;8;难|C5;8;得|C5;8;沉|C5;8;默|C4;8|E4;8|G4;8;秋|E5;8;风|
D5;8;厌|C5;8;倦|C5;8;漂|C5;8;泊|D4;8|F4;8|G4;8;夕|E5;8;阳|
D5;8;赖|C5;8;着|C5;8;不|C5;8;走|D5;8;挂|D5;8;在|D5;8;墙|C5;8;头|
D5;8;舍|E5;8;不|E5;8;得|E5;8;我|E4;8|G4;8|C5;8;昔|A5;8;日|
A5;8;伊|A5;8;人|A5;8;耳|A5;8;边|A5;4;话|A5;8;已|E5;8;和|
G5;8;潮|G5;8;声|G5;8;向|A5;8;东|G5;4;流|G4;8;再|E5;8;回|
F5;8;首|A4;8;|F5;8;往|E5;8;事|F5;8;也|E5;8;随|D5;8;枫|C5;8;叶|
C5;8;一|D5;8;片|D5;8;片|D5;8;落|D4;4|G4;8;爱|E5;8;已|
D5;8;走|C5;8;到|C5;8;尽|C5;8;头|C4;8|E4;8|G4;8;恨|E5;8;也|
D5;8;放|C5;8;弃|C5;8;承|C5;8;诺|D4;8|F4;8|G4;8;命|E5;8;运|
D5;8;自|C5;8;认|C5;8;幽|C5;8;默|D5;8;想|D5;8;法|D5;8;太|C5;8;多|
D5;8;由|E5;8;不|E5;8;得|E5;8;我|E4;8|G4;8|C5;8;壮|A5;8;志|
A5;8;凌|A5;8;云|A5;8;几|A5;8;分|A5;4;愁|A5;8;知|E5;8;己|
G5;8;难|G5;8;逢|G5;8;几|A5;8;人|G5;4;留|G4;8;再|E5;8;回|
F5;8;首|A4;8;|F5;8;确|E5;8;闻|F5;8;笑|E5;8;传|D5;8;醉|C5;8;梦|
P;8|G5;4;中|P;4|
C4;8|C5;8;笑|C5;8;谈|D5;8;词|E5;8;穷|G4;8|E5;8;古|G5;8;痴|
A5;8;今|P;16|B5;16;狂|A5;8;终|G5;8;成|E5;8;空|G4;8|B4;4|
F4;8|C5;8;刀|C5;8;钝|D5;8;刃|E5;4;乏|D5;8;恩|C5;8;断|
E5;8;义|G5;8;绝|G5;8;梦|A5;8;方|D5;8;破|G4;8|B4;4|
E4;8|E5;8;路|E5;8;荒|F5;8;已|G5;8;叹|B4;8|G5;8;饱|E5;8;览|
B5;8;足|A5;8;迹|B5;8;没|C6;8;人|B5;8;懂|A5;8|A4;8|C5;8|
F4;8|A5;8;多|A5;8;年|G5;8;望|G5;8;眼|P;16|E4;16;欲|D5;8;穿|C5;8;过|
D5;8;红|D5;16;尘|E5;16|D5;8;滚|C5;8;滚|D5;8;我|D5;16;没|E5;16|D5;8;看|C5;8;透|
C4;4|P;4|P;4|P;4
"#;
/*
自嘲末尽千情万缘已皆愁
曲终人散发花鬓白红颜殁
烛残未觉与日争辉徒消瘦
当泪干血隐狂涌白雪纷飞都成空
*/

/// 《梁祝》
pub const LIANG_ZHU:&str = r#"
E4;4|G4;8|P;16|A4;16|C5,C4;8|E4;16|D5;16|A4;16|C5;16|G4;8|
G5,C4;8|G4;16|C6;16|A5;16|G5;16|E5;16|G5;16|D4,D5;8|G4;8|A4;8|C5;8|
D4,D5;8|D5;16|E5;16|D4,B4;8|A4;8|C4,E4,G4;8|P;16|A4;16|C5,E4;8|D5;8|
E4;8|C5;8|A4,C4;16|G4;16|A4;16|C5;16|G4;8|C6;8|A5;16|G5;16|A5;16|C6;16|
E5,C4;8|G4;16|G5;16|B4;8|D5;8|A4,E4;16|C5;16|G4;8|P;4|
C4,E4;16|P;32|G4;16|E4;8|E4;8|G4;16|A4;16|B4;16|D5;16|A4,E4;8|E4;8|C4;16|E4;16|G4;16|A4;16|
C5,C4;8|G4;16|D5;16|G5;8|E5;8|G4,B4,D5;8|E5;16|D5;16|C5;8|A4;16|G4;16|
E4;4|C5;4|A4,F4;16|P;32|C5;32|A4;16|G4;16|E4;16|G4;16|A4;16|C5;16|
D4,G4;8|D4;8|G4;8|E5;16|G5;16|D5;16|E5;16|D5;16|C5;16|B4;8|A4;8|
E4;4|G4;8|P;16|A4;16|C5,C4;8|E4;16|D5;16|A4;16|C5;16|G4;8|
G5,C4;8|G4;16|C6;16|A5;16|G5;16|E5;16|G5;16|D4,D5;8|G4;8|A4;8|C5;8|
D4,D5;8|D5;16|E5;16|D4,B4;8|A4;8|C4,E4,G4;8|P;16|A4;16|C5,E4;8|D5;8|
E4;8|C5;8|A4,C4;16|G4;16|A4;16|C5;16|G4;8|C6;8|A5;16|G5;16|A5;16|C6;16|
E5,C4;8|G4;16|G5;16|B4;8|D5;8|A4,E4;16|C5;16|G4;8|P;4|
C4,E4;16|P;32|G4;32|E4;8|G4;16|A4;16|B4;16|D5;16|A4,E4;8|E4;8|C4;16|E4;16|G4;16|A4;16|
C5,C4;8|G4;16|D5;16|G5;8|E5;8|G4,B4,D5;8|E5;16|D5;16|C5;8|A4;16|G4;16|
E4;4|C5;4|A4,F4;16|P;32|C5;32|A4;16|G4;16|E4;16|G4;16|A4;16|C5;16|
D4,G4;8|D4;8|G4;8|E5;16|G5;16|D5;16|E5;16|D5;16|C5;16|B4;8|A4;8|
D4,G4;4|P;8|E5;16|G5;16|D5;16|E5;16|D5;16|C5;16|B4;8|D5;8
"#;

/// 《但愿人长久》
pub const DAN_YUAN_REN_CHANG_JIU:&str = r#"
C5,C4;8;明|E4;8|C5;8;月|A4;8|G4;8;几|C4;8|A4;8;时|C5;8|
C5,A4,C4;8;有|E4;8|A4;8|B4;4|E4;8|A4;8|C4;8|
C5,A4,F4;8;把|C4;8|C5;8;酒|A4;8|G4;8;问|C4;8|A4;8;青|D5;8|
D4,G4,B4,D5;4;天|A4,F4;4|D4,G4;4|D4,B4;4|
E5,C5,A4;8;不|E4;8|C5;8;知|A4;8|E5;8;天|E4;8|C5;8;上|A4;8|
D4,D5;8;宫|F4;8|A4;8|C5;8|A4,E4;4;阙|C4;4|
F4,F5;8;今|A4;8|F5;4;夕|A4;8;是|C5;4;何|D5;8;年|
D4;8|G4;8|B4;8|D5;4|B4;8|A4;8|B4;8|
C5,C4;8;我|E4;8|C5;8;欲|A4;8;乘|G4;8;风|C4;8;归|A4;8|C5;8|
C4,A4,C4;8;去|E4;8|A4;8|B4;4|E4;8|B4;8|A4;8|
C5,A4,F4;8;唯|C4;8|C5;8;恐|A4;8;琼|G4;8;楼|C4;8|A4;8;玉|D5;8|
D4,G4,B4,D5;4;宇|A4,F4;4|D4,G4;4|D4,B4;4|
E5,C5,A4;8;高|E4;8|C5;8;处|A4;8|E5;8;不|E4;8|C5;8;胜|A4;8|
D4,D5;8;寒|F4;8|A4;8|C5;8|A4,E4;4|C4;4|
F4,F5;8;起|A4;8|F5;4;舞|A4;8;弄|C5;4;清|D5;8;影|
D4;8|G4;8|B4;8|D5;4|G4;8|D4;8|G4;8|
F4,D5;4;何|G4;4;似|B4;8;在|A4;4;人|B4;8|
C5,C4;8;间|G4;8|C5;8|D5;8|E5;8|G4;8|D5;8|C5;8|
E5,E4;8;转|D5;8|E5;8|D5;8|E5,C4;8;朱|E4;8|C5;4;阁|
F4,F5;8;低|A4;8|G5;8;绮|F5;8|E5,E4;8;户|D5;8|C5;4|
G4,B4,D5;8;照|D4;8|F4;8|G4;8|B4;8|G5;8;无|A5;8|G5;8|
G4,B4,D5;8;眠|D4;8|G4;8|B4;4|D4;8|A4;8|G4;8|
E5,E4;8;不|D5;8|E5;8;应|D5;8|E5,C4;8;有|E4;8|C5;4;恨|
F4,F5;8;何|A4;8|G5;8;事|F5;8;长|E5,E4;8;向|D5;8|C5;4|
G4,B4,D5;8;别|D4;8|G4;8|B4;4|G5;8;时|A5;8|G5;8|
G4,B4,D5;8;圆|D4;8|G4;8|B4;4|B4;8|A4;8|B4;8|
C5,C4;8;人|E4;8|C5;8;有|A4;8;悲|G4;8;欢|C4;8|A4;8;离|C5;8|
C5,A4,C4;8;合|E4;8|A4;8|B4;4|E4;8|B4;8|A4;8|
C5,A4,F4;8;月|C4;8|C4;8;有|A4;8;阴|G4;8;晴|C4;8|A4;8;圆|D5;8|
D4,G4,B4,D5;4;缺|A4,F4;4|D4,G4;4|D4,B4;4|
E5,C5,A4;8;此|E4;8|C5;8;事|A4;8|E5;8;古|E4;8|C5;8;难|A4;8|
D4,D5;8;全|F4;8|A4;8|C5;8|A4,E4;4|C4;4|
F4,F5;8;但|A4;8|F5;4;愿|A4;8;人|C5;4;长|D5;8;久|
D4;8|G4;8|B4;8|D5;4|G4;8|D4;8|G4;8|
F4,D5;4;千|G4;4;里|B4;8;共|A4;4;婵|B4;8|
C5,C4;8;娟|G4;8|C5;8|D5;8|E5;8|G4;8|D5;8|C5;8|
C5,C4,E4,G4;4
            "#;


#[derive(Debug, Clone)]
pub struct Tab{
    pub tones: Vec<(String, usize)>,
    pub time: f64,
    pub word: String,
}

pub fn get_index(key:&str) -> Option<usize>{
    for k in KEYS.iter().enumerate(){
        if k.1 == &key{
            return Some(k.0);
        }
    }
    None
}

pub fn parse_tabs(s: &str) -> Option<Vec<Tab>>{
    let mut tabs = vec![];
    //每组音符
    for tab in s.split("|").map(|t| t.trim()){
        let mut tab = tab.split(";");
        tabs.push(Tab{
            //每组中的所有音符
            tones: tab.next()?.split(",").map(|t|{
                let index = get_index(&t).unwrap_or(0);
                // ConsoleService::log(&format!("索引: {} {}", t, index));
                let name = t.to_string();
                (name, index)
            }).collect(),
            //这一组音符的时长
            time: tab.next()?.parse::<u8>().map_or_else(|_| None, |v| Some(v as f64))?,
            //这一组音符的歌词
            word: tab.next().unwrap_or("").to_string()
        });
    }
    Some(tabs)
}

pub struct Phenotype{
    pub color: JsValue,
    pub x: f64,
    pub y: f64,
    pub width: f64,
    pub height: f64,
    /// 音符 P为休止符
    pub tone: String,
    /// 歌词
    pub word: String,
}

impl Phenotype{
    pub fn update(&mut self){
        self.y += 1.5;
    }

    pub fn render(&self, ctx: &CanvasRenderingContext2d){

        if self.tone == "P"{
            return;
        }

        // if self.word.is_empty(){
        //     ctx.set_fill_style(&JsValue::from_str("gray"));
        // }else{
            ctx.set_fill_style(&self.color);
        // }
        
        ctx.fill_rect(self.x, self.y, self.width, self.height);
        ctx.set_font(&format!("{}pt Arial", 20));
        ctx.set_fill_style(&JsValue::from_str("white"));
        ctx.fill_text(&format!("{}", self.word), 10., self.y).unwrap();
        // ConsoleService::log(&format!("{}x{}", self.x, self.y))
    }
}